home *** CD-ROM | disk | FTP | other *** search
- MODULE M2Init;
-
- (*
- * Stand: 29.10.95
- *
- * Initialisierungs-Routine für MM2-Programme.
- * Sie ist für normale Programme und Accessories geeignet.
- *
- * Dieses Modul muß in der Regel als erstes Treibermodul beim Linken
- * von MM2-Programmen eingebunden werden. Es wird dann beim Start des
- * Programms angesprungen und erhält in folgenden Registern definierte Werte:
- * A0: Bei ACCs die Adresse der Base Page, sonst Null.
- * A1: Zeiger auf eine Liste von Adressen aller Modulkörper.
- * A2: Zeiger auf den im Prg-code abgelegten PDB (Daten d. residenten Module)
- *
- * Der Stack-Pointer ist bei ACCs noch nicht definiert, zuerst muß ein
- * Speicherbereich alloziert werden, in den dann der Stack gelegt wird.
- *
- * Bei normalen Programmen ist A7 bereits definiert, bei 4(A7) befindet
- * sich der Zeiger auf die Base Page. Das Programm wird immer in den
- * größten freien Speicherbereich geladen, der dann schon alloziert ist.
- * Mit dem 'Mshrink'-Aufruf wird der Bereich soweit verkleinert, daß nur
- * noch der benötigte Platz für den Programmcode, Base Page, glob. Variable
- * und den Stack verbleiben. Der Stack-Pointer, der zuerst auf das Ende des
- * Bereichs zeigt, wird dann ans Ende des neuen, verkleinerten Bereichs
- * gesetzt.
- *
- * Auf die untere Grenze des Stack-Bereichs wird immer das A3-Register
- * gesetzt.
- *
- * Einige Daten im PDB werden für das Laufzeitsystem (z.B. MOSCtrl, PrgCtrl)
- * und die Modulverwaltung (Loader/ModCtrl/ModBase) initialisiert.
- *
- * Dann werden die Module intialisiert, die von M2Init importiert werden.
- * Dazu werden alle Adressen angesprungen, die in der Liste der Modulkörper
- * (A1 zeigt darauf) stehen. Das Ende der Liste ist mit einer Null gekenn-
- * zeichnet. Der Aufruf "PushPDB" schließt die Initialisierung des Laufzeit-
- * systems ab.
- *
- * Nun können die restlichen Modulkörper ausgeführt werden. Deren Adressen
- * folgen in der schon erwähnten Liste. Dabei werden zuerst die weiteren
- * Treibermodule mitsamt ihrer Importe und ganz zuletzt das Hauptmodul
- * gestartet. Wenn es zurückkehrt, ist die Modulkörperliste zuende und
- * das Programm terminiert.
- *
- * ----------------------------------------------------------------------------
- * 18.12.90 Fertigstellung für System 2.2
- * 14.02.91 Der PDB wird nun im BSS- statt im TEXT-Segment angelegt.
- * 17.01.94 Die Pterm-Routine von GEMDOS wird nicht mehr direkt angesprungen.
- * 29.10.95 Auf dem Stack werden 32 Byte Platz gelassen, damit es keine
- * "Memory Violation" unter MiNT mit aktivem Speicherschutz gibt.
- *)
-
- (*$ M- Keine Symbole ablegen *)
- (*$ N+ Runtime-Modul nicht automatisch importieren *)
- (*$ L- Für Assembler: Keine Codeerzeugung vom Compiler am Prozedurbeginn *)
-
- FROM SYSTEM IMPORT ASSEMBLER, BYTE, TSIZE;
-
- FROM MOSCtrl IMPORT PDB, PushPDB, SetProcessState, ProcessID, Pterm;
-
- (* Storage/StorBase darf nicht importiert werden! *)
-
- CONST (* default size of stack for process *)
- stackSize = 8192;
-
- (* base page constants *)
- codestart = 8;
- codelen = 12;
- datastart = 16;
- datalen = 20;
- bssstart = 24;
- bsslen = 28;
- parent = 36;
-
- (* GEMDOS functions *)
- Malloc = $48;
- Mshrink = $4A;
-
-
- VAR basePDB: PDB;
-
- BEGIN
- ASSEMBLER
- MOVE.L A1,A6 ; A6: address of main module entries
-
- ; first copy preset PDB (A2) to 'basePDB' (A4)
- LEA basePDB,A4
- MOVEQ #TSIZE(PDB) DIV 2 - 1,D0
- copyPDB MOVE.W (A2)+,(A4)+
- DBRA D0,copyPDB
- LEA basePDB,A4 ; A4 now points to PDB
-
- MOVE.L A0,D0 ; base page for accessory in A0?
- BNE initAcc ; yes
-
- ; initialization for normal programs
- MOVE.L 4(A7),A5
- MOVE.L codelen(A5),D0
- ADD.L datalen(A5),D0
- ADD.L bsslen(A5),D0
- ADDI.L #256,D0 ; D0: total length of static program space
- MOVE.L D0,D2
- ADD.L A5,D2 ; D2: end of program space
- ADDQ.L #1,D2
- BCLR #0,D2 ; sync D2
- MOVE.L D2,A3 ; end of prg.space is bottom of stack
- MOVE.L PDB.topOfStack(A4),D3
- BEQ useDefault
- ADD.L D3,D0
- BRA gotStack
- useDefault:
- ADDI.L #stackSize,D0
- gotStack:
- MOVE.L D0,D1 ; D0: size of prg.space + stack
- ADD.L A5,D1 ; D1: top of stack
- ADDQ.L #1,D1
- BCLR #0,D1 ; sync D1
- CMP.L A7,D1 ; enough stack ?
- BHI oldStack
- MOVE.L D1,A7 ; set new top of stack
- oldStack:
- MOVE.L D0,-(A7) ; new workspace of process
- MOVE.L A5,-(A7) ; starting address of workspace
- CLR.W -(A7)
- MOVE #Mshrink,-(A7) ; return unused memory
- TRAP #1
- ADDA.W #12,A7
- BRA contNorm
-
- initAcc ; initialization for accessories
- MOVE.L A0,A5 ; address of base page
- LEA 256(A5),A7 ; use top of basepage's cmdline as stack
- MOVE.L PDB.topOfStack(A4),D0
- BNE takeIt
- MOVE.L #stackSize,D0
- takeIt: MOVE.L D0,-(A7)
- MOVE #Malloc,-(A7)
- TRAP #1
- ADDQ.L #2,A7
- MOVE.L (A7)+,D1 ; size of stack
- TST.L D0 ; bottom address of stack
- BLE.W error ; not enough memory
- MOVE.L D0,A3 ; bottom of stack -> A3
- ADD.L D1,D0
- MOVE.L D0,A7 ; top of stack -> A7
-
- contNorm:
- MOVE.L A5,PDB.basePageAddr(A4) ; store ^base page
- SUBA.W #32,A7 ; TT 29.10.95 added
- MOVE.L A7,A1 ; get stack pointer
- SUBA.W #12,A1 ; point to process return address,
- MOVE.L A1,PDB.topOfStack(A4) ; process needs it to return on error
- MOVE.L A3,PDB.bottomOfStack(A4) ; lowest address of stack
-
- ; init modules imported by this module
- loop1 MOVE.L (A6)+,A0
- MOVE.L A0,D0 ; end of list ?
- BEQ end1
- MOVEM.L A4/A6,-(A7)
- JSR (A0) ; call bodies
- MOVEM.L (A7)+,A4/A6
- BRA loop1
-
- end1: MOVE.L A4,(A3)+
- MOVE.L ProcessID,A0
- MOVE.L (A0),(A3)+
- JSR PushPDB ; determine local process-id
-
- MOVE #1,(A3)+
- JSR SetProcessState ; init-phase
- loop2: MOVE.L (A6)+,A0
- MOVE.L A0,D0 ; end of list ?
- BEQ end2
- TST.L (A6) ; last module ?
- BNE notLast
- MOVE.L A0,-(A7)
- MOVE #2,(A3)+
- JSR SetProcessState ; run-phase
- MOVE.L (A7)+,A0
- notLast MOVEM.L A4/A6,-(A7)
- JSR (A0) ; call main modules
- MOVEM.L (A7)+,A4/A6
- BRA loop2
-
- error: MOVE #-39,(A3)+
- BRA exit
- end2: CLR (A3)+
- exit: JMP Pterm ; terminate process
- END
- END M2Init.
-